﻿using Microsoft.IdentityModel.Tokens;
using System;
using System.Collections.Generic;
using System.IdentityModel.Tokens.Jwt;
using System.Linq;
using System.Security.Claims;
using System.Text;
using System.Threading.Tasks;

namespace RandomDemo.TokenFiles
{
    public static class Token
    {
        /// <summary>
        /// 创建token
        /// </summary>
        /// <param name="jwt">字典</param>
        /// <returns></returns>
        public static string CreateToken(JwtPayload jwt)
        {
            //引用System.IdentityModel.Tokens.Jwt
            DateTime utcNow = DateTime.UtcNow;
            //string key = "f47b558d-7654-458c-99f2-13b190ef0199";
            SecurityKey securityKey = new SymmetricSecurityKey(Encoding.ASCII.GetBytes(TokenConfig.SecurityKey));

            var claims = new List<Claim>()
            {
                //new Claim("Id",userId.ToString()),
                //new Claim("user_id",userId.ToString()),
                //new Claim("user_info",userinfo.ToString()),
                //new Claim(ClaimTypes.Role,RoleId.ToString())
            };

            foreach (var item in jwt)
            {
                claims.Add(new Claim(item.Key, item.Value.ToString()));
            }
            JwtSecurityToken jwtToken = new JwtSecurityToken(
                issuer: TokenConfig.Issuer,
                audience: TokenConfig.Audience,
                claims: claims,
                notBefore: utcNow,
                expires: utcNow.AddMinutes(TokenConfig.Expires),
                signingCredentials: new SigningCredentials(securityKey, SecurityAlgorithms.HmacSha256)
                );

            //生成token方式1
            string token1 = new JwtSecurityTokenHandler().WriteToken(jwtToken);
            SingTon.Instence.Jwts.Add(jwtToken);
            //A Microsoft.IdentityModel.Tokens.SecurityTokenDescriptor that contains details of contents of the token.
            return token1;

        }
        /// <summary>
        /// token验证并转换为字符串
        /// </summary>
        /// <param name="token"></param>
        /// <returns>返回解密的token，通过json转换为UserIdentity对象，就可以遍历AdditionalData中来得到user_indo（自定义的数据）</returns>
        public static string Validata(string token)
        {
            //校验token
            var validateParameter = new TokenValidationParameters()
            {
                ValidateLifetime = true,
                ValidateAudience = true,
                ValidateIssuer = true,
                ValidateIssuerSigningKey = true,
                ValidIssuer = TokenConfig.Issuer,
                ValidAudience = TokenConfig.Audience,
                IssuerSigningKey = new SymmetricSecurityKey(Encoding.ASCII.GetBytes(TokenConfig.SecurityKey)),
            };
            //不校验，直接解析token
            //jwtToken = new JwtSecurityTokenHandler().ReadJwtToken(token1);
            try
            {
                //校验并解析token
                var claimsPrincipal = new JwtSecurityTokenHandler().ValidateToken(token, validateParameter, out SecurityToken validatedToken);//validatedToken:解密后的对象
                var jwtPayload = ((JwtSecurityToken)validatedToken).Payload.SerializeToJson(); //获取payload中的数据 
                return jwtPayload;
            }
            catch (SecurityTokenExpiredException)
            {
                //表示过期
                return "token过期";
            }
            catch (SecurityTokenException)
            {
                //表示token错误
                return "token验证错误";
            }
        }

        public static string RefreshToken(string token, double expires)
        {
            //校验token
            var validateParameter = new TokenValidationParameters()
            {
                ValidateLifetime = true,
                ValidateAudience = true,
                ValidateIssuer = true,
                ValidateIssuerSigningKey = true,
                ValidIssuer = TokenConfig.Issuer,
                ValidAudience = TokenConfig.Audience,
                IssuerSigningKey = new SymmetricSecurityKey(Encoding.ASCII.GetBytes(TokenConfig.SecurityKey)),
            };
            //不校验，直接解析token
            //jwtToken = new JwtSecurityTokenHandler().ReadJwtToken(token1);
            try
            {
                //校验并解析token
                var claimsPrincipal = new JwtSecurityTokenHandler().ValidateToken(token, validateParameter, out SecurityToken validatedToken);//validatedToken:解密后的对象
                var index = SingTon.Instence.Jwts.IndexOf((JwtSecurityToken)validatedToken);
                if (index == -1)
                {
                    return "token验证错误";
                }
                var jwtPayload = ((JwtSecurityToken)validatedToken).Payload.SerializeToJson(); //获取payload中的数据 
                return jwtPayload;
            }
            catch (SecurityTokenExpiredException)
            {
                //表示过期
                return "token过期";
            }
            catch (SecurityTokenException)
            {
                //表示token错误
                return "token验证错误";
            }
            //var jwtToken = _jwtToken;
            //jwtToken.ValidTo.AddMinutes(expires);
            //return new JwtSecurityTokenHandler().WriteToken(jwtToken);
        }
    }

    public static class TokenConfig
    {
        public static string SecurityKey = "f47b558d-7654-458c-99f2-13b190ef0199";
        public static string Issuer = "user";
        public static string Audience = "pulei";
        public static Double Expires = 200;
    }
}
